﻿using Newtonsoft.Json.Linq;
using SoftHelper.Model;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace SoftHelper.Tool
{
    public class IOTool
    {
        public IList<FileInfo> FilesList = new List<FileInfo>();
        private List<String> FilesType;

        /// <summary>
        /// 获取项目中的所有文件行数
        /// </summary>
        /// <param name="list"></param>
        /// <returns></returns>
        public static async Task<int> getProjectCodeLines(IList<FileInfo> list)
        {

            int codeLines = 0;
            foreach (var item in list)
            {
                StreamReader streamReader = new StreamReader(item.FullName);
                while (await streamReader.ReadLineAsync() != null)
                {
                    codeLines++;
                }
            }
            return codeLines;
        }

        /// <summary>
        /// 获取项目中的所有字符数
        /// </summary>
        /// <param name="fileSystems"></param>
        /// <returns></returns>
        public static async Task<long> getProjectChars(IList<FileInfo> fileSystems)
        {
            long sumChars = 0;
            foreach (FileSystemInfo fileSystemInfo in fileSystems)
            {
                StreamReader streamReader = new StreamReader((string)fileSystemInfo.FullName);
                String str = await streamReader.ReadToEndAsync();
                sumChars += str.ToCharArray().Length;
            }
            return sumChars;
        }


        /// <summary>
        /// 设置文件筛选规则
        /// </summary>
        /// <param name="FilesType"></param>
        public void SetFilesType(List<String> FilesType)
        {
            this.FilesType = FilesType;
        }


        /// <summary>
        /// 获取指定文件夹下的所有文件
        /// </summary>
        /// <param name="fullpath">指定的路径</param>
        public async void getAllFiles(string fullpath)
        {
            try
            {
                /*如果不设置文件筛选规则*/
                if (FilesType==null)
                {
                    FilesType = new List<string>();
                    //获取读入规则
                    String json = await IOTool.ToRead(System.Windows.Forms.Application.StartupPath + "/languageTypesConfig.json");
                    JObject jobject = JObject.Parse(json);
                    IList<JToken> jTokens = jobject["LanguageTypes"].Children().ToList();
                    foreach (JToken jToken in jTokens)
                    {
                        TagContainerItemModel model = jToken.ToObject<TagContainerItemModel>();
                        FilesType.Add(model.Name);
                    }
                }

                DirectoryInfo dirs = new DirectoryInfo(fullpath);
                DirectoryInfo[] dir = dirs.GetDirectories();//获取当前目录下的子目录
                FileInfo[] file = dirs.GetFiles();   //放回当前目录的文件列表
                int dircount = dir.Count();  //获取文件夹对象数量
                int filecount = file.Count(); //获取文件数量
                //循环文件夹
                for (int i = 0; i < dircount; i++)
                {
                    if (!dir[i].Name.Contains('.'))
                    {
                        string pathnode = fullpath + "\\" + dir[i].Name;
                        GetMultiNode(pathnode);

                    }
                }
                //循环文件
                for (int j = 0; j < filecount; j++)
                {
                    if (file[j].FullName.Contains('.'))
                    {
                        addFileInfoInList(file[j], FilesType);
                    }
                }
            }
            catch
            {

            }
        }

        public void GetMultiNode(string path)
        {
            DirectoryInfo directoryInfo = new DirectoryInfo(path);
            DirectoryInfo[] DirectoryInfo = directoryInfo.GetDirectories();
            FileInfo[] fileInfos = directoryInfo.GetFiles();
            foreach (DirectoryInfo item in DirectoryInfo)
            {
                GetMultiNode(item.FullName);
            }

            foreach (FileInfo item in fileInfos)
            {
                if (item.FullName.Contains('.'))
                    addFileInfoInList(item, FilesType);
            }
        }

        /// <summary>
        /// 依据规则添加入库
        /// </summary>
        /// <param name="fileInfo"></param>
        public void addFileInfoInList(FileInfo fileInfo, List<String> NeedFiles)
        {
            foreach (String item in NeedFiles)
            {
                if (fileInfo.Name.Substring(fileInfo.Name.LastIndexOf('.') + 1) == item)
                {
                    FilesList.Add(fileInfo);
                }
            }

        }


        /// <summary>
        /// 分析出项目的主要语言
        /// </summary>
        public static ProjectLanguageModel AnalysisProjectLanguage(IList<FileInfo> fileSystems)
        {
            ProjectLanguageModel projectLanguageModel = new ProjectLanguageModel();
            bool isFirst = true;
            KeyValuePair<String, Double> target = new KeyValuePair<string, Double>();
            Dictionary<String, Double> message = new Dictionary<string, Double>();
            foreach (FileInfo filesystem in fileSystems)
            {
                String fileType = filesystem.Name.Substring(filesystem.Name.LastIndexOf('.') + 1);
                if (!message.Keys.Contains(fileType))
                {
                    message.Add(fileType, 1);
                }
                else
                {
                    message[fileType] += 1;

                }
            }


            foreach (KeyValuePair<String, Double> item in message)
            {
                if (isFirst)
                {
                    target = item;
                    isFirst = false;
                }

                if (item.Value > target.Value)
                {
                    target = item;
                }
            }
            projectLanguageModel.Language = target.Key;
            projectLanguageModel.FileTypeDictionary = message;
            return projectLanguageModel;
        }

        /// <summary>
        /// 写文件
        /// </summary>
        /// <param name="filePath"></param>
        /// <param name="content"></param>
        public static async Task ToWrite(String filePath, String content)
        {
            FileStream fileStream = new FileStream(filePath, FileMode.Create);
            StreamWriter streamWriter = new StreamWriter(fileStream);
            await streamWriter.WriteAsync(content);
            streamWriter.Close();
            fileStream.Close();
        }

        /// <summary>
        /// 读文件
        /// </summary>
        /// <param name="path"></param>
        /// <returns></returns>
        public static async Task<String> ToRead(String filePath)
        {
            FileStream fileStream = new FileStream(filePath, FileMode.Open);
            StreamReader streamReader = new StreamReader(fileStream);
            String content = streamReader.ReadToEnd();
            streamReader.Close();
            return content;
        }

    }
}
